#ifndef _TEST_CHAT_CLIENT_H_
#define _TEST_CHAT_CLIENT_H_

#include <strstream>
using namespace std;

#include "hy_msg.h"
#include "hy_session.h"
#include "hy_rw_helper.h"
#include "hy_enter_packet_tactics.h"
#include "hy_reactor.h"

class hy_chat_client : public hy_session
{
	typedef hy_msg_pool	block_pool_t;
	typedef hy_chat_client service_t;
public:
	class hy_chat_input : public hy_enter_packet_input<service_t>
	{
	public:
		hy_chat_input(service_t* service,hy_handle_base* hb)
			:hy_enter_packet_input<service_t>(service,hb)
		{

		}	
	};

	class hy_chat_output: public hy_enter_packet_output<service_t>
	{
	public:
		hy_chat_output(service_t* service,hy_handle_base* hb)
			:hy_enter_packet_output<service_t>(service,hb)
		{

		}	
	};

	class hy_chat_state: public hy_session_state<service_t>
	{
	public:
		hy_chat_state(service_t* service,hy_handle_base* hb)
			:hy_session_state<service_t>(service,hb)
		{

		}	
	};
public:
	hy_chat_client(hy_reactor* reactor,const char* ip,hy_u32_t port)
		:_count(0),input(this,this),output(this,this),_state(this,this)
		,_ip(ip),_port(port),_conned(hls_close)
	{
		hy_handle_link::init(reactor,&input,&output,&_state);
	}

	void process(hy_msg* msg)
	{
		//hy_trace("socket[%s] receive msg:[%d]",msg->rptr(),_socket);
		msg->reference(false);
	}

	hy_err_t pop(hy_msg*& buff,hy_u32_t len)
	{
		return _blocks.create(len,buff);
	}
	void connect()
	{
		this->conn(_ip.data(),_port);
	}

	void chat()
	{
		if (_conned != hls_conned)
		{
			return;
		}
		_count++;
		strstream ss;
		ss<<_socket<<":robotchat."<<_count;
		std::string str;
		ss>>str;
		//hy_trace("send msg[%s]",str.data());

		hy_msg *msg = NULL;
		if (pop(msg,128) == hy_right)
		{			
			hy_rwblock_helper iomsg(msg);
			iomsg<<str.data();
			this->send(msg);
		}
	}
	void state(hy_handle_base* hb,hy_link_state sc,hy_link_state ec)
	{
		_conned = ec;
		if (ec == hls_conned)
		{
			hy_trace("chat client conn success");
			chat();
		}
		else
		{
			hy_trace("chat client conn failed");
		}
	}
public:
	std::string				_ip;
	hy_u32_t				_port;

	hy_i32_t				_conned;

	hy_u32_t				_count;
	block_pool_t			_blocks;
	hy_chat_input			input;
	hy_chat_output			output;
	hy_chat_state			_state;
};
#endif  //_TEST_CHAT_CLIENT_H_
